package com.keya.utils;

import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.annotation.TableName;
import io.swagger.annotations.ApiModelProperty;
import lombok.extern.slf4j.Slf4j;

import java.lang.reflect.Field;

/**
 * 创建数据库表工具类.
 *
 * @author : xf.he
 * @version : 1.0 2023/4/17
 * @since : 1.0
 **/
@Slf4j
public class CreateTableUtil<T> {

    /**
     * Java实体转mysql建表
     *
     * @param clazz        需要转的实体对象
     * @param isCreateTime 是否需要生成创建人，创建时间等信息
     */
    public static <T> String createTableSql(Class<T> clazz, boolean isCreateTime) {
        TableName model = clazz.getAnnotation(TableName.class);
        Field[] fields = clazz.getDeclaredFields();
        String param;
        String cameCaseColumn;
        String underScoreCaseColumn;
        StringBuilder sql = new StringBuilder();
        //以下生成建表Sql
        sql.append("create table ").append(model.value()).append("(\n");
        sql.append("id int not NULL AUTO_INCREMENT COMMENT '主键id',\n");
        for (Field f : fields) {
            cameCaseColumn = f.getName();
            underScoreCaseColumn = cameCaseColumn;
            for (int i = 0; i < cameCaseColumn.length(); i++) {
                if (Character.isUpperCase(cameCaseColumn.charAt(i))) {
                    // 将javabean中小驼峰命名变量的“大写字母”转换为“_小写字母”
                    underScoreCaseColumn = underScoreCaseColumn.replaceAll("([A-Z])", "_$1").toLowerCase();
                }
            }
            param = f.getType().getTypeName();
            //得到ApiModelProperty 注解的value
            ApiModelProperty apiModelProperty = f.getAnnotation(ApiModelProperty.class);
            switch (param) {
                case "java.lang.Integer":
                    sql.append(underScoreCaseColumn).append(" ")
                            .append("int(8) DEFAULT NULL COMMENT '")
                            .append(ObjectUtil.isNotEmpty(apiModelProperty) ? apiModelProperty.value() : "")
                            .append("',\n");
                    break;
                case "java.lang.Boolean":
                    sql.append(underScoreCaseColumn)
                            .append(" ")
                            .append("tinyint(1) DEFAULT NULL COMMENT '")
                            .append(ObjectUtil.isNotEmpty(apiModelProperty) ? apiModelProperty.value() : "")
                            .append("',\n");
                    break;
                case "java.math.BigDecimal":
                    sql.append(underScoreCaseColumn)
                            .append(" ")
                            .append("decimal(18,2) DEFAULT NULL COMMENT '")
                            .append(ObjectUtil.isNotEmpty(apiModelProperty) ? apiModelProperty.value() : "")
                            .append("',\n");
                    break;
                case "java.util.Date":
                    sql.append(underScoreCaseColumn)
                            .append(" ")
                            .append("datetime DEFAULT NULL COMMENT '")
                            .append(ObjectUtil.isNotEmpty(apiModelProperty) ? apiModelProperty.value() : "")
                            .append("',\n");
                    break;
                default:
                    sql.append(underScoreCaseColumn)
                            .append(" ")
                            .append("VARCHAR(255) DEFAULT NULL COMMENT '")
                            .append(ObjectUtil.isNotEmpty(apiModelProperty) ? apiModelProperty.value() : "")
                            .append("',\n");
            }
        }
        if (isCreateTime) {
            sql.append("sys_deleted tinyint(1) DEFAULT '0' COMMENT '删除状态，1删除 0正常',\n");
            sql.append("sys_created datetime NOT NULL COMMENT '创建时间',\n");
            sql.append("sys_created_by varchar(32) NOT NULL COMMENT '创建人',\n");
            sql.append("sys_modified datetime NOT NULL COMMENT '更新时间',\n");
            sql.append("sys_modified_by varchar(32) NOT NULL COMMENT '更新人',\n");
        }
        sql.append("PRIMARY KEY (id) USING BTREE");
        //sql.delete(sql.lastIndexOf(","), sql.length());
        sql.append("\n)ENGINE=INNODB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_bin COMMENT='")
                .append(model.value())
                .append("';");
        return sql.toString();
    }

}
